const http = require('http');
const request = require('request');
const spawn = require('child_process').spawn;

class MyWatchServer {
    /**
     * @param port      当前服务的端口
     * @param target    测试访问对象数组
     * @param nextTime  一次测试访问后多久再次发起测试访问
     * @param index     索引，用于优先级(按1，2，3，4给就好)
     * @param checkHost 一个函数，用于检查发起请求者（避免外部访问使用，但是可能没必要也没完善）
     */
    constructor(port,target,nextTime,index,checkHost) {
        this.port = port;
        this.checkHost = checkHost || (() => true);
        this.nextTime = nextTime || 60 * 1000;
        this.target = target.map((_,index) => {
            return {
                url: _.url,
                command: _.command,
                index
            }
        });
        this.init();
        setTimeout(this.checkTarget.bind(this),this.nextTime);
        this.index = index || 1;
        this.count = 0;
    }

    init() {
        let $this = this;
        http.createServer((req, res) => {
            res.writeHead(200, { 'Content-Type': 'text/plain; charset=UTF-8' });
            if (this.checkHost(req.headers.host)) {
                res.end(JSON.stringify({code: 200}));
            } else {
                res.end(JSON.stringify({code: -1}));
            }
        }).listen(this.port,function () {
            console.log(`The service is start success , port is ${$this.port}.`);
        });
    }

    checkTarget() {
        let $this = this;
        $this.target.forEach(_ => {
            this.testOneServe(_);
        });
    }

    testOneServe({ url , command, index }) {
        let next = (function() {
            setTimeout(this.testOneServe.bind(this,{ url , command, index }),this.nextTime);
        }).bind(this);
        let $this = this;

        request({
            url
        },function (err) {
            if (err) {
                // 需要重启
                console.log(`访问 ${url} 失败，请求重新启动,err:${err.message}`);
                $this.count++;
                if (1 === $this.index) {
                    spawn('start cmd /k ' + command,{
                        shell: true
                    });
                } else {
                    if ($this.count % $this.index) {
                        console.log(`按照索引值，需要在第 ${$this.index - $this.count % $this.index} 次轮询后才能发起启动命令`);
                    } else {
                        spawn('start cmd /k ' + command,{
                            shell: true
                        });
                    }
                }
            } else {
                $this.count = 0;
                console.log(`访问 ${url} 正常`);
                // 一般也就这样
                //if (body === 'ok') {}
            }
            next();
        });
    }
}

module.exports = MyWatchServer;